
package io.lettuce.core.api.coroutines

import io.lettuce.core.ExperimentalLettuceCoroutinesApi
import io.lettuce.core.FlushMode
import io.lettuce.core.FunctionRestoreMode
import io.lettuce.core.ScriptOutputType

/**
 * Coroutine executed commands for Redis Functions. [java.lang.String Function code] is encoded by using the configured
 * [io.lettuce.core.ClientOptions#getScriptCharset charset].
 *
 * @param <K> Key type.
 * @param <V> Value type.
 * @author Mark Paluch
 * @since 6.3
 * @generated by io.lettuce.apigenerator.CreateKotlinCoroutinesApi
 */
@ExperimentalLettuceCoroutinesApi
interface RedisFunctionCoroutinesCommands<K : Any, V : Any> {

    /**
     * Invoke a function.
     *
     * @param function the function name.
     * @param type output type.
     * @param keys key names.
     * @param <T> expected return type.
     * @return function result.
     */
    suspend fun <T : Any> fcall(
        function: String,
        type: ScriptOutputType,
        vararg keys: K
    ): T?

    /**
     * Invoke a function.
     *
     * @param function the function name.
     * @param type output type.
     * @param keys the keys.
     * @param values the values (arguments).
     * @param <T> expected return type.
     * @return function result.
     */
    suspend fun <T : Any> fcall(
        function: String,
        type: ScriptOutputType,
        keys: Array<K>,
        vararg values: V
    ): T?

    /**
     * Invoke a function in read-only mode.
     *
     * @param function the function name.
     * @param type output type.
     * @param keys key names.
     * @param <T> expected return type.
     * @return function result.
     */
    suspend fun <T : Any> fcallReadOnly(
        function: String,
        type: ScriptOutputType,
        vararg keys: K
    ): T?

    /**
     * Invoke a function in read-only mode.
     *
     * @param function the function name.
     * @param type output type.
     * @param keys the keys.
     * @param values the values (arguments).
     * @param <T> expected return type.
     * @return function result.
     */
    suspend fun <T : Any> fcallReadOnly(
        function: String,
        type: ScriptOutputType,
        keys: Array<K>,
        vararg values: V
    ): T?

    /**
     * Load a library to Redis.
     *
     * @param functionCode code of the function.
     * @return name of the library.
     */
    suspend fun functionLoad(functionCode: String): String?

    /**
     * Load a library to Redis.
     *
     * @param functionCode code of the function.
     * @param replace whether to replace an existing function.
     * @return name of the library.
     */
    suspend fun functionLoad(functionCode: String, replace: Boolean): String?

    /**
     * Return the serialized payload of loaded libraries. You can restore the dump through {@link #functionRestore(byte[])}.
     *
     * @return the serialized payload.
     */
    suspend fun functionDump(): ByteArray?

    /**
     * You can restore the dumped payload of loaded libraries.
     *
     * @return Simple string reply
     */
    suspend fun functionRestore(dump: ByteArray): String?

    /**
     * You can restore the dumped payload of loaded libraries.
     *
     * @return Simple string reply
     */
    suspend fun functionRestore(dump: ByteArray, mode: FunctionRestoreMode): String?

    /**
     * Deletes all the libraries using the specified [FlushMode].
     *
     * @param flushMode the flush mode (sync/async).
     * @return String simple-string-reply.
     */
    suspend fun functionFlush(flushMode: FlushMode): String?

    /**
     * Kill a function that is currently executing.
     *
     * @return String simple-string-reply.
     */
    suspend fun functionKill(): String?

    /**
     * Return information about the functions and libraries.
     *
     * @return Array reply.
     */
    suspend fun functionList(): List<Map<String, Any>>

    /**
     * Return information about the functions and libraries.
     *
     * @param libraryName specify a pattern for matching library names.
     * @return Array reply.
     */
    suspend fun functionList(libraryName: String): List<Map<String, Any>>

}

